<template>
  <PageWrapper title="表单基础示例" contentFullHeight>
    <CollapseContainer title="基础示例">
      <BasicForm
        autoFocusFirstItem
        :labelWidth="200"
        :schemas="schemas"
        :actionColOptions="{ span: 24 }"
        @submit="handleSubmit"
        @reset="handleReset"
      >
        <template #selectA="{ model, field }">
          <a-select
            :options="optionsA"
            mode="multiple"
            v-model:value="model[field]"
            @change="valueSelectA = model[field]"
            allowClear
          />
        </template>
        <template #selectB="{ model, field }">
          <a-select
            :options="optionsB"
            mode="multiple"
            v-model:value="model[field]"
            @change="valueSelectB = model[field]"
            allowClear
          />
        </template>
        <template #localSearch="{ model, field }">
          <ApiSelect
            :api="optionsListApi"
            showSearch
            v-model:value="model[field]"
            optionFilterProp="label"
            resultField="list"
            labelField="name"
            valueField="id"
          />
        </template>
        <template #remoteSearch="{ model, field }">
          <ApiSelect
            :api="optionsListApi"
            showSearch
            v-model:value="model[field]"
            :filterOption="false"
            resultField="list"
            labelField="name"
            valueField="id"
            :params="searchParams"
            @search="onSearch"
          />
        </template>
      </BasicForm>
    </CollapseContainer>
  </PageWrapper>
</template>
<script lang="ts">
import { computed, defineComponent, unref, ref } from 'vue'
import { BasicForm, FormSchema, ApiSelect } from '@/components/form/index'
import { CollapseContainer } from '@/components/container'
import { useMessage } from '@/hooks/web/useMessage'
import { PageWrapper } from '@/components/page'
import { optionsListApi, treeOptionsListApi } from '@pkg/apis/demo'
import { Select } from 'ant-design-vue'
import { cloneDeep } from '@pkg/utils'
import { useDebounceFn } from '@pkg/use'

const valueSelectA = ref<string[]>([])
const valueSelectB = ref<string[]>([])
const options = ref<Recordable[]>([])
for (let i = 1; i < 10; i++)
  options.value.push({ label: '选项' + i, value: `${i}` })

const optionsA = computed(() => {
  return cloneDeep(unref(options)).map((op) => {
    op.disabled = unref(valueSelectB).indexOf(op.value) !== -1
    return op
  })
})
const optionsB = computed(() => {
  return cloneDeep(unref(options)).map((op) => {
    op.disabled = unref(valueSelectA).indexOf(op.value) !== -1
    return op
  })
})

const provincesOptions = [
  {
    id: 'guangdong',
    label: '广东省',
    value: '1',
    key: '1',
  },
  {
    id: 'jiangsu',
    label: '江苏省',
    value: '2',
    key: '2',
  },
]
const citiesOptionsData = {
  guangdong: [
    {
      label: '珠海市',
      value: '1',
      key: '1',
    },
    {
      label: '深圳市',
      value: '2',
      key: '2',
    },
    {
      label: '广州市',
      value: '3',
      key: '3',
    },
  ],
  jiangsu: [
    {
      label: '南京市',
      value: '1',
      key: '1',
    },
    {
      label: '无锡市',
      value: '2',
      key: '2',
    },
    {
      label: '苏州市',
      value: '3',
      key: '3',
    },
  ],
}

const schemas: FormSchema[] = [
  {
    field: 'divider-basic',
    component: 'Divider',
    label: '基础字段',
  },
  {
    field: 'field1',
    component: 'Input',
    label: '字段1',

    colProps: {
      span: 8,
    },
    // componentProps:{},
    // can func
    componentProps: ({ schema, formModel }) => {
      console.log('form:', schema)
      console.log('formModel:', formModel)
      return {
        placeholder: '自定义placeholder',
        onChange: (e: any) => {
          console.log(e)
        },
      }
    },
    renderComponentContent: () => {
      return {
        prefix: () => 'pSlot',
        suffix: () => 'sSlot',
      }
    },
  },
  {
    field: 'field2',
    component: 'Input',
    label: '带后缀',
    defaultValue: '111',
    colProps: {
      span: 8,
    },
    componentProps: {
      onChange: (e: any) => {
        console.log(e)
      },
    },
    suffix: '天',
  },
  {
    field: 'field3',
    component: 'DatePicker',
    label: '字段3',
    colProps: {
      span: 8,
    },
  },
  {
    field: 'field4',
    component: 'Select',
    label: '字段4',
    colProps: {
      span: 8,
    },
    componentProps: {
      options: [
        {
          label: '选项1',
          value: '1',
          key: '1',
        },
        {
          label: '选项2',
          value: '2',
          key: '2',
        },
      ],
    },
  },
  {
    field: 'field5',
    component: 'CheckboxGroup',
    label: '字段5',
    colProps: {
      span: 8,
    },
    componentProps: {
      options: [
        {
          label: '选项1',
          value: '1',
        },
        {
          label: '选项2',
          value: '2',
        },
      ],
    },
  },
  {
    field: 'field7',
    component: 'RadioGroup',
    label: '字段7',
    colProps: {
      span: 8,
    },
    componentProps: {
      options: [
        {
          label: '选项1',
          value: '1',
        },
        {
          label: '选项2',
          value: '2',
        },
      ],
    },
  },
  {
    field: 'field8',
    component: 'Checkbox',
    label: '字段8',
    colProps: {
      span: 8,
    },
    renderComponentContent: 'Check',
  },
  {
    field: 'field9',
    component: 'Switch',
    label: '字段9',
    colProps: {
      span: 8,
    },
  },
  {
    field: 'field10',
    component: 'RadioButtonGroup',
    label: '字段10',
    colProps: {
      span: 8,
    },
    componentProps: {
      options: [
        {
          label: '选项1',
          value: '1',
        },
        {
          label: '选项2',
          value: '2',
        },
      ],
    },
  },
  {
    field: 'field11',
    component: 'Cascader',
    label: '字段11',
    colProps: {
      span: 8,
    },
    componentProps: {
      options: [
        {
          value: 'zhejiang',
          label: 'Zhejiang',
          children: [
            {
              value: 'hangzhou',
              label: 'Hangzhou',
              children: [
                {
                  value: 'xihu',
                  label: 'West Lake',
                },
              ],
            },
          ],
        },
        {
          value: 'jiangsu',
          label: 'Jiangsu',
          children: [
            {
              value: 'nanjing',
              label: 'Nanjing',
              children: [
                {
                  value: 'zhonghuamen',
                  label: 'Zhong Hua Men',
                },
              ],
            },
          ],
        },
      ],
    },
  },
  {
    field: 'divider-api-select',
    component: 'Divider',
    label: '远程下拉演示',
  },
  {
    field: 'field30',
    component: 'ApiSelect',
    label: '懒加载远程下拉',
    required: true,
    componentProps: {
      // more details see /src/components/Form/src/components/ApiSelect.vue
      api: optionsListApi,
      params: {
        id: 1,
      },
      resultField: 'list',
      // use name as label
      labelField: 'name',
      // use id as value
      valueField: 'id',
      // not request untill to select
      immediate: false,
      onChange: (e) => {
        console.log('selected:', e)
      },
      // atfer request callback
      onOptionsChange: (options) => {
        console.log('get options', options.length, options)
      },
    },
    colProps: {
      span: 8,
    },
    defaultValue: '0',
  },
  {
    field: 'field31',
    component: 'Input',
    label: '下拉本地搜索',
    helpMessage: [
      'ApiSelect组件',
      '远程数据源本地搜索',
      '只发起一次请求获取所有选项',
    ],
    required: true,
    slot: 'localSearch',
    colProps: {
      span: 8,
    },
    defaultValue: '0',
  },
  {
    field: 'field32',
    component: 'Input',
    label: '下拉远程搜索',
    helpMessage: ['ApiSelect组件', '将关键词发送到接口进行远程搜索'],
    required: true,
    slot: 'remoteSearch',
    colProps: {
      span: 8,
    },
    defaultValue: '0',
  },
  {
    field: 'field33',
    component: 'ApiTreeSelect',
    label: '远程下拉树',
    helpMessage: ['ApiTreeSelect组件', '使用接口提供的数据生成选项'],
    required: true,
    componentProps: {
      api: treeOptionsListApi,
      resultField: 'list',
    },
    colProps: {
      span: 8,
    },
  },
  {
    field: 'field34',
    component: 'ApiRadioGroup',
    label: '远程Radio',
    helpMessage: ['ApiRadioGroup组件', '使用接口提供的数据生成选项'],
    required: true,
    componentProps: {
      api: optionsListApi,
      params: {
        count: 2,
      },
      resultField: 'list',
      // use name as label
      labelField: 'name',
      // use id as value
      valueField: 'id',
    },
    defaultValue: '1',
    colProps: {
      span: 8,
    },
  },
  {
    field: 'field35',
    component: 'ApiRadioGroup',
    label: '远程Radio',
    helpMessage: ['ApiRadioGroup组件', '使用接口提供的数据生成选项'],
    required: true,
    componentProps: {
      api: optionsListApi,
      params: {
        count: 2,
      },
      resultField: 'list',
      // use name as label
      labelField: 'name',
      // use id as value
      valueField: 'id',
      isBtn: true,
    },
    colProps: {
      span: 8,
    },
  },
  {
    field: 'divider-linked',
    component: 'Divider',
    label: '字段联动',
  },
  {
    field: 'province',
    component: 'Select',
    label: '省份',
    colProps: {
      span: 8,
    },
    componentProps: ({ formModel, formActionType }) => {
      return {
        options: provincesOptions,
        placeholder: '省份与城市联动',
        onChange: (e: any) => {
          // console.log(e)
          let citiesOptions =
            e == 1
              ? citiesOptionsData[provincesOptions[0].id]
              : citiesOptionsData[provincesOptions[1].id]
          // console.log(citiesOptions)
          if (e === undefined) {
            citiesOptions = []
          }
          formModel.city = undefined //  reset city value
          const { updateSchema } = formActionType
          updateSchema({
            field: 'city',
            componentProps: {
              options: citiesOptions,
            },
          })
        },
      }
    },
  },
  {
    field: 'city',
    component: 'Select',
    label: '城市',
    colProps: {
      span: 8,
    },
    componentProps: {
      options: [], // defalut []
      placeholder: '省份与城市联动',
    },
  },
  {
    field: 'divider-selects',
    component: 'Divider',
    label: '互斥多选',
    helpMessage: ['两个Select共用数据源', '但不可选择对方已选中的项目'],
  },
  {
    field: 'selectA',
    component: 'Select',
    label: '互斥SelectA',
    slot: 'selectA',
    defaultValue: [],
    colProps: {
      span: 8,
    },
  },
  {
    field: 'selectB',
    component: 'Select',
    label: '互斥SelectB',
    slot: 'selectB',
    defaultValue: [],
    colProps: {
      span: 8,
    },
  },
  {
    field: 'divider-others',
    component: 'Divider',
    label: '其它',
  },
  {
    field: 'field20',
    component: 'InputNumber',
    label: '字段20',
    required: true,
    colProps: {
      span: 8,
    },
  },
  {
    field: 'field21',
    component: 'Slider',
    label: '字段21',
    componentProps: {
      min: 0,
      max: 100,
      range: true,
      marks: {
        20: '20°C',
        60: '60°C',
      },
    },
    colProps: {
      span: 8,
    },
  },
  {
    field: 'field22',
    component: 'Rate',
    label: '字段22',
    defaultValue: 3,
    colProps: {
      span: 8,
    },
    componentProps: {
      disabled: false,
      allowHalf: true,
    },
  },
]

export default defineComponent({
  components: {
    BasicForm,
    CollapseContainer,
    PageWrapper,
    ApiSelect,
    ASelect: Select,
  },
  setup() {
    const check = ref(null)
    const { createMessage } = useMessage()
    const keyword = ref<string>('')
    const searchParams = computed<Recordable>(() => {
      return { keyword: unref(keyword) }
    })

    function onSearch(value: string) {
      keyword.value = value
    }
    return {
      schemas,
      optionsListApi,
      optionsA,
      optionsB,
      valueSelectA,
      valueSelectB,
      onSearch: useDebounceFn(onSearch, 300),
      searchParams,
      handleReset: () => {
        keyword.value = ''
      },
      handleSubmit: (values: any) => {
        createMessage.success('click search,values:' + JSON.stringify(values))
      },
      check,
    }
  },
})
</script>
